; ModuleID = 'ub.c'
target datalayout = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-a0:0:64-f80:32:32-n8:16:32"
target triple = "i386-pc-linux-gnu"

%struct.ompi_communicator_t = type opaque
%struct.ompi_datatype_t = type opaque
%struct.ompi_predefined_communicator_t = type opaque
%struct.ompi_predefined_datatype_t = type opaque

@ompi_mpi_comm_world = external global %struct.ompi_predefined_communicator_t
@ompi_mpi_float = external global %struct.ompi_predefined_datatype_t
@ompi_mpi_ub = external global %struct.ompi_predefined_datatype_t
@.str = private constant [14 x i8] c"Process %d > \00", align 1
@.str1 = private constant [7 x i8] c"%4.1f \00", align 1

define i32 @main(i32 %argc, i8** %argv) nounwind {
entry:
  %argc_addr = alloca i32, align 4
  %argv_addr = alloca i8**, align 4
  %retval = alloca i32
  %p = alloca i32
  %my_rank = alloca i32
  %block_lengths = alloca [2 x i32]
  %displacements = alloca [2 x i32]
  %types = alloca [2 x %struct.ompi_datatype_t*]
  %vector_mpi_t = alloca %struct.ompi_datatype_t*
  %ub_mpi_t = alloca %struct.ompi_datatype_t*
  %count = alloca i32
  %padded_size = alloca i32
  %stride = alloca i32
  %input_data = alloca [12 x float]
  %local_data = alloca [12 x float]
  %i = alloca i32
  %io_comm = alloca %struct.ompi_communicator_t*
  %"alloca point" = bitcast i32 0 to i32
  store i32 %argc, i32* %argc_addr
  store i8** %argv, i8*** %argv_addr
  %0 = call i32 @MPI_Init(i32* %argc_addr, i8*** %argv_addr) nounwind
  %1 = call i32 @MPI_Comm_size(%struct.ompi_communicator_t* bitcast (%struct.ompi_predefined_communicator_t* @ompi_mpi_comm_world to %struct.ompi_communicator_t*), i32* %p) nounwind
  %2 = call i32 @MPI_Comm_rank(%struct.ompi_communicator_t* bitcast (%struct.ompi_predefined_communicator_t* @ompi_mpi_comm_world to %struct.ompi_communicator_t*), i32* %my_rank) nounwind
  %3 = call i32 @MPI_Comm_dup(%struct.ompi_communicator_t* bitcast (%struct.ompi_predefined_communicator_t* @ompi_mpi_comm_world to %struct.ompi_communicator_t*), %struct.ompi_communicator_t** %io_comm) nounwind
  store i32 12, i32* %padded_size, align 4
  %4 = load i32* %p, align 4
  %5 = load i32* %padded_size, align 4
  %6 = sdiv i32 %5, %4
  store i32 %6, i32* %count, align 4
  %7 = load i32* %p, align 4
  store i32 %7, i32* %stride, align 4
  %8 = load i32* %count, align 4
  %9 = load i32* %stride, align 4
  %10 = call i32 @MPI_Type_vector(i32 %8, i32 1, i32 %9, %struct.ompi_datatype_t* bitcast (%struct.ompi_predefined_datatype_t* @ompi_mpi_float to %struct.ompi_datatype_t*), %struct.ompi_datatype_t** %vector_mpi_t) nounwind
  %11 = load %struct.ompi_datatype_t** %vector_mpi_t, align 4
  %12 = getelementptr inbounds [2 x %struct.ompi_datatype_t*]* %types, i32 0, i32 0
  store %struct.ompi_datatype_t* %11, %struct.ompi_datatype_t** %12, align 4
  %13 = getelementptr inbounds [2 x %struct.ompi_datatype_t*]* %types, i32 0, i32 1
  store %struct.ompi_datatype_t* bitcast (%struct.ompi_predefined_datatype_t* @ompi_mpi_ub to %struct.ompi_datatype_t*), %struct.ompi_datatype_t** %13, align 4
  %14 = getelementptr inbounds [2 x i32]* %displacements, i32 0, i32 0
  store i32 0, i32* %14, align 4
  %15 = getelementptr inbounds [2 x i32]* %displacements, i32 0, i32 1
  store i32 4, i32* %15, align 4
  %16 = getelementptr inbounds [2 x i32]* %block_lengths, i32 0, i32 1
  store i32 1, i32* %16, align 4
  %17 = getelementptr inbounds [2 x i32]* %block_lengths, i32 0, i32 1
  %18 = load i32* %17, align 4
  %19 = getelementptr inbounds [2 x i32]* %block_lengths, i32 0, i32 0
  store i32 %18, i32* %19, align 4
  %block_lengths1 = bitcast [2 x i32]* %block_lengths to i32*
  %displacements2 = bitcast [2 x i32]* %displacements to i32*
  %types3 = bitcast [2 x %struct.ompi_datatype_t*]* %types to %struct.ompi_datatype_t**
  %20 = call i32 @MPI_Type_struct(i32 2, i32* %block_lengths1, i32* %displacements2, %struct.ompi_datatype_t** %types3, %struct.ompi_datatype_t** %ub_mpi_t) nounwind
  %21 = call i32 @MPI_Type_commit(%struct.ompi_datatype_t** %ub_mpi_t) nounwind
  %22 = load i32* %my_rank, align 4
  %23 = icmp eq i32 %22, 0
  br i1 %23, label %bb, label %bb6

bb:                                               ; preds = %entry
  store i32 0, i32* %i, align 4
  br label %bb5

bb4:                                              ; preds = %bb5
  %24 = load i32* %i, align 4
  %25 = load i32* %i, align 4
  %26 = sitofp i32 %25 to float
  %27 = getelementptr inbounds [12 x float]* %input_data, i32 0, i32 %24
  store float %26, float* %27, align 4
  %28 = load i32* %i, align 4
  %29 = add nsw i32 %28, 1
  store i32 %29, i32* %i, align 4
  br label %bb5

bb5:                                              ; preds = %bb4, %bb
  %30 = load i32* %i, align 4
  %31 = load i32* %padded_size, align 4
  %32 = icmp slt i32 %30, %31
  br i1 %32, label %bb4, label %bb6

bb6:                                              ; preds = %bb5, %entry
  %33 = load %struct.ompi_communicator_t** %io_comm, align 4
  %34 = load i32* %p, align 4
  %35 = load i32* %padded_size, align 4
  %36 = sdiv i32 %35, %34
  %37 = load %struct.ompi_datatype_t** %ub_mpi_t, align 4
  %input_data7 = bitcast [12 x float]* %input_data to float*
  %input_data78 = bitcast float* %input_data7 to i8*
  %local_data9 = bitcast [12 x float]* %local_data to float*
  %local_data910 = bitcast float* %local_data9 to i8*
  %38 = call i32 @MPI_Scatter(i8* %input_data78, i32 1, %struct.ompi_datatype_t* %37, i8* %local_data910, i32 %36, %struct.ompi_datatype_t* bitcast (%struct.ompi_predefined_datatype_t* @ompi_mpi_float to %struct.ompi_datatype_t*), i32 0, %struct.ompi_communicator_t* %33) nounwind
  %39 = load i32* %my_rank, align 4
  %40 = call i32 (i8*, ...)* @printf(i8* noalias getelementptr inbounds ([14 x i8]* @.str, i32 0, i32 0), i32 %39) nounwind
  store i32 0, i32* %i, align 4
  br label %bb12

bb11:                                             ; preds = %bb12
  %41 = load i32* %i, align 4
  %42 = getelementptr inbounds [12 x float]* %local_data, i32 0, i32 %41
  %43 = load float* %42, align 4
  %44 = fpext float %43 to double
  %45 = call i32 (i8*, ...)* @printf(i8* noalias getelementptr inbounds ([7 x i8]* @.str1, i32 0, i32 0), double %44) nounwind
  %46 = load i32* %i, align 4
  %47 = add nsw i32 %46, 1
  store i32 %47, i32* %i, align 4
  br label %bb12

bb12:                                             ; preds = %bb11, %bb6
  %48 = load i32* %p, align 4
  %49 = load i32* %padded_size, align 4
  %50 = sdiv i32 %49, %48
  %51 = load i32* %i, align 4
  %52 = icmp sgt i32 %50, %51
  br i1 %52, label %bb11, label %bb13

bb13:                                             ; preds = %bb12
  %53 = call i32 @putchar(i32 10) nounwind
  %54 = call i32 @MPI_Finalize() nounwind
  br label %return

return:                                           ; preds = %bb13
  %retval14 = load i32* %retval
  ret i32 %retval14
}

declare i32 @MPI_Init(i32*, i8***)

declare i32 @MPI_Comm_size(%struct.ompi_communicator_t*, i32*)

declare i32 @MPI_Comm_rank(%struct.ompi_communicator_t*, i32*)

declare i32 @MPI_Comm_dup(%struct.ompi_communicator_t*, %struct.ompi_communicator_t**)

declare i32 @MPI_Type_vector(i32, i32, i32, %struct.ompi_datatype_t*, %struct.ompi_datatype_t**)

declare i32 @MPI_Type_struct(i32, i32*, i32*, %struct.ompi_datatype_t**, %struct.ompi_datatype_t**)

declare i32 @MPI_Type_commit(%struct.ompi_datatype_t**)

declare i32 @MPI_Scatter(i8*, i32, %struct.ompi_datatype_t*, i8*, i32, %struct.ompi_datatype_t*, i32, %struct.ompi_communicator_t*)

declare i32 @printf(i8* noalias, ...) nounwind

declare i32 @putchar(i32)

declare i32 @MPI_Finalize()
